package cn.yto.print.socket;

import cn.hutool.json.JSONUtil;
import cn.yto.print.model.request.CameraLoginRequest;
import cn.yto.print.model.request.CameraOsdRequest;
import cn.yto.print.model.request.CameraRequest;
import cn.yto.print.model.response.CameraResponse;
import cn.yto.print.service.CameraDeviceService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import javax.websocket.*;
import javax.websocket.server.ServerEndpoint;
import java.util.Objects;
import java.util.concurrent.CopyOnWriteArraySet;

@Slf4j
@Component
@ServerEndpoint(value = "/camera")
public class CameraSocketEndpoint {

    private static final CopyOnWriteArraySet<CameraSocketEndpoint> SOCKET_SET = new CopyOnWriteArraySet<>();

    private static CameraDeviceService cameraDeviceService;

    private Session session;

    @Autowired
    public void setCameraDeviceService(CameraDeviceService cameraDeviceService) {
        CameraSocketEndpoint.cameraDeviceService = cameraDeviceService;
    }

    @OnOpen
    public void onOpen(Session session) {
        this.session = session;
        SOCKET_SET.add(this);
        log.info("前端摄像头通道连接建立，会话ID：{}，连接数 : {}", session.getId(), CameraSocketEndpoint.SOCKET_SET.size());
        sendMessage(JSONUtil.toJsonStr(new CameraResponse(CameraResponse.SUCCESS_CODE, "连接成功")));
    }

    @OnMessage
    public void onMessage(String message, Session session) {
        CameraResponse response = null;
        String messageType = null;
        try {
            CameraRequest cameraMessage = JSONUtil.toBean(message, CameraRequest.class);
            messageType = cameraMessage.getType();
            if (messageType.equals(CameraRequest.CAMERA_LOGIN)) {
                CameraLoginRequest loginRequest = JSONUtil.toBean(cameraMessage.getContent(), CameraLoginRequest.class);
                response = cameraDeviceService.login(loginRequest);
            } else if (messageType.equals(CameraRequest.CAMERA_OSD)) {
                CameraOsdRequest osdRequest = JSONUtil.toBean(cameraMessage.getContent(), CameraOsdRequest.class);
                response = cameraDeviceService.cameraOsd(osdRequest);
            }
        } catch (Exception e) {
            log.error("处理前端摄像头请求消息异常", e);
            response = new CameraResponse(CameraResponse.FAILURE_CODE, "系统处理异常");
        }

        if (null != response) {
            sendMessage(JSONUtil.toJsonStr(new CameraRequest(messageType, JSONUtil.toJsonStr(response))));
        }
    }

    @OnClose
    public void onClose(Session session, CloseReason reason) {
        SOCKET_SET.remove(this);
        log.info("前端摄像头通道连接断开，会话ID：{}，连接数：{}", session.getId(), CameraSocketEndpoint.SOCKET_SET.size());
    }

    @OnError
    public void onError(Session session, Throwable error) {
        log.error("前端摄像头通道连接发生异常", error);
    }

    /**
     * 发送消息
     */
    public void sendMessage(String message) {
        try {
//            this.session.getBasicRemote().sendText(message);
            this.session.getAsyncRemote().sendText(message);
            log.info("发送前端摄像头响应报文：{}", message);
        } catch (Exception e) {
            log.error("发送前端摄像头响应报文异常: ", e);
        }
    }

}
